﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using CakeLibrary;
using Medianamik.Core.Sugar;

namespace Medianamik.UI.Mediasend.Logic
{
    public class MediasendMailing
    {
        private readonly MediasendSession _session;
        public int ID { get; private set; }
        public MediasendCampaign Campaign { get; private set; }
        public int? ListId { get; set; }
        public int? SubListId { get; set; }
        public MailingStatus Status { get; private set; }
        public DateTime CreatedOn { get; private set; }
        public string Name { get; set; }
        public string Subject { get; set; }
        public string Message { get; set; }
        public string SenderName { get; set; }
        public string SenderEmail { get; set; }

        internal MediasendMailing(MediasendSession session, int id, MediasendCampaign campaign, int listId, MailingStatus status, DateTime createdOn, string name, string subject, string message)
        {
            _session = session;
            ID = id;
            Campaign = campaign;
            ListId = listId;
            Status = status;
            CreatedOn = createdOn;
            Name = name;
            Subject = subject;
            Message = message;
            SenderName = string.Empty;
            SenderEmail = string.Empty;
        }

        internal static MailingStatus ToMediasendStatus(string status)
        {
            return (MailingStatus)Enum.Parse(typeof(MailingStatus), status, true);
        }

        internal static string ToCakeMailStatus(MailingStatus status)
        {
            var name = status.ToString();
            var index = 1;
            foreach(var c in name.Substring(index))
            {
                if (char.IsUpper(c))
                    name = name.Insert(index, "_");
                ++index;    
            }
            return name.ToLower();
        }

        internal static MediasendMailing MakeMailing(MediasendSession session, MediasendCampaign campaign, int listId, Dictionary<string, object> record)
        {
            return new MediasendMailing(session,
                                        int.Parse(record["id"].ToString()),
                                        campaign,
                                        listId,
                                        ToMediasendStatus(record["status"].ToString()),
                                        DateTime.Parse(record["created_on"].ToString()),
                                        record["name"].ToString(),
                                        record["subject"].ToString(),
                                        record["html_message"].ToString());
        }

        private Dictionary<string, object> MakeDictionary()
        {
            return new Dictionary<string, object>
                {
                    { "campaign_id", Campaign.ID.ToString() },
                    { "list_id", ListId.ToString() },
                    { "sublist_id", SubListId.HasValue ? SubListId.ToString() : "" },
                    { "name", Name },
                    { "subject", Subject },
                    { "html_message", Message},
                    { "sender_name", SenderName },
                    { "sender_email", SenderEmail }
                };
        }

        public bool Send()
        {
            return Schedule(null);
        }

        public bool Schedule(DateTime? when)
        {
            try
            {
                var dict = _session.MakeBaseDictionary();
                dict.Add("mailing_id", ID.ToString());
                if (when.HasValue && when.Value > DateTime.Now)
                    dict.Add("date", when.Value.ToString("dd-MM-yyyy HH:mm:ss"));
                CakeMailing.Schedule(dict);
                return true;
            }
            catch (CakeException ex)
            {
                _session.LastError = ex.Message;
                return false;
            }
        }

        public bool SendTest(string email)
        {
            return SendTest(email, TestEmailType.Merged);
        }

        public bool SendTest(string email, TestEmailType type)
        {
            try
            {
                var dict = _session.MakeBaseDictionary();
                dict.Add("mailing_id", ID.ToString());
                dict.Add("test_email", email);
                dict.Add("test_type", type.ToString().ToLower());
                CakeMailing.SendTestEmail(dict);
                return true;
            }
            catch (CakeException ex)
            {
                _session.LastError = ex.Message;
                return false;
            }
        }

        public bool Save()
        {
            try
            {
                var dict = _session.MakeBaseDictionary();
                dict.Add("mailing_id", ID.ToString());
                dict.AddRange(MakeDictionary());
                CakeMailing.SetInfo(dict);
                return true;
            }
            catch (CakeException ex)
            {
                _session.LastError = ex.Message;
                return false;
            }
        }

        public bool Delete()
        {
            return _session.DeleteMailing(this);
        }
    }

    public enum MailingStatus
    {
        Archived,
        Incomplete,
        Scheduled,
        Delivering,
        Delivered,
        Deleted
    }

    public enum TestEmailType
    {
        Merged,
        Separated
    }
}
